import { Show } from "@/component/Display";
import { GlobalValue } from "@/GlobalValue";
import { IViewComponentProps, views_factory } from "@/Factory";
import classNames from "classnames";
import { HTMLAttributes, useMemo } from "react";
import { ContentView } from "./ContentView";
import { DockType } from "./DockType";
import { IEditorInfo } from "./IEditorInfo";
import styles from "./style.module.scss";
import { IHandleDropdownItemClick, TabBar } from "./TabBar";
import { Slot } from "../WorkspacesView";
import ErrorBoundary from "antd/es/alert/ErrorBoundary";
import { Paths } from "@/paths";
export interface IEditorViewProps extends HTMLAttributes<HTMLDivElement>, IViewComponentProps {
  actived?: boolean;
  ref_dragging?: React.RefObject<[Slot, IEditorInfo] | undefined>;
  on_tab_drag_start?(info: IEditorInfo): void;
  on_tab_drag_end?(info: IEditorInfo): void;
  on_somethings_drop_to_tabs?(pair: [index: number, prev: IEditorInfo | undefined, next: IEditorInfo | undefined]): void,
  on_somethings_drop_to_content?(dock_type: DockType): void,
  on_dropdown_item_click?: IHandleDropdownItemClick<IEditorInfo>;
}
export function EditorView(props: IEditorViewProps) {
  const {
    children, ws_slot, actived,
    ref_dragging,
    on_tab_drag_start,
    on_tab_drag_end,
    on_somethings_drop_to_tabs,
    on_somethings_drop_to_content,
    on_dropdown_item_click,
    ..._p
  } = props;
  const [{ slot_infos: slots }, , dispatch] = GlobalValue.use()

  const slot: GlobalValue.IEditorsSlotInfo | undefined = useMemo(() => {
    if (!ws_slot) return void 0
    return slots[ws_slot.id]
  }, [ws_slot, slots])


  const handle_actived = (actived: IEditorInfo) => {
    if (!slot) return;
    const new_slot: GlobalValue.IEditorsSlotInfo = { ...slot, actived }
    dispatch([GlobalValue.Type.SetSlotInfos, [new_slot]])
  }

  const handle_deleted = (info: IEditorInfo) => {
    if (!slot) return;
    const editors = slot.editors.filter(v => v.uid !== info.uid)
    if (!editors.length) {
      ws_slot?.workspaces.del(ws_slot.id)
      ws_slot?.workspaces.confirm()
      dispatch([GlobalValue.Type.DelSlotInfos, [slot.id]])
      return;
    }

    const new_slot: GlobalValue.IEditorsSlotInfo = { ...slot, editors }
    if (info.uid === slot.actived?.uid) {
      const idx = slot.editors.findIndex(v => v.uid === info.uid);
      new_slot.actived = editors[idx] ?? editors[idx - 1]
    }
    dispatch([GlobalValue.Type.SetSlotInfos, [new_slot]])
  }
  const hasPermission = Paths.usePermission();
  const root_classname = classNames(styles.editor_view, { [styles.editor_view_actived]: actived })
  const Cls = views_factory.find_component(slot?.actived?.kind)
  return (
    <div className={root_classname} {..._p}>
      <Show yes={!!slot?.editors.length}>
        <TabBar
          infos={slot?.editors}
          actived={slot?.actived}
          on_actived={handle_actived}
          on_deleted={handle_deleted}
          on_tab_drag_start={on_tab_drag_start}
          on_tab_drag_end={on_tab_drag_end}
          on_somethings_drop={on_somethings_drop_to_tabs}
          on_dropdown_item_click={on_dropdown_item_click} />
      </Show>
      <ContentView
        actived_tab={slot?.actived}
        tabs={slot?.editors}
        ref_dragging={ref_dragging}
        ws_slot={ws_slot}
        on_somethings_drop={on_somethings_drop_to_content}>
        <ErrorBoundary key={slot?.actived?.uid}>
          {
            hasPermission(slot?.actived?.kind) ? (
              <Cls
                ws_slot={ws_slot}
                key={slot?.actived?.uid}
                actived={true}
                info={slot?.actived}
              />
            ) : (
              <Paths.NoPermission pathname={slot?.actived?.kind} />
            )
          }
        </ErrorBoundary>
      </ContentView>
    </div >
  )
}